﻿using BaseExtendsions;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using Newtonsoft.Json.Serialization;


/// <summary>
/// 
/// </summary>
public static class JSON
{

    /// <summary>
    /// 
    /// </summary>
    private static JsonSerializerSettings jsonSerializerSettings;
    /// <summary>
    /// 
    /// </summary>
    public static JsonSerializerSettings JsonSerializerSettings
    {
        get
        {
            if (jsonSerializerSettings == null)
            {
                jsonSerializerSettings = new JsonSerializerSettings();

                jsonSerializerSettings.SetSetting();
            }
            return jsonSerializerSettings;
        }
        //set
        //{
        //    if (jsonSerializerSettings == null)
        //    {
        //        jsonSerializerSettings = new JsonSerializerSettings();
        //        jsonSerializerSettings.SetSetting();
        //    }
        //}
    }
    /// <summary>
    /// 序列号
    /// </summary>
    /// <param name="value"></param>
    public static string Serialize(object? value)
    {
        return JsonConvert.SerializeObject(value, JsonSerializerSettings);
    }
    /// <summary>
    /// 序列号
    /// </summary>
    /// <param name="value"></param>
    /// <param name="propertyNames">包括的属性名称</param>
    public static string Serialize(object value, List<string> propertyNames)
    {
        JsonSerializerSettings.ContractResolver = new JsonPropertyContractResolver(propertyNames);
        var s = JsonConvert.SerializeObject(value, JsonSerializerSettings);
        JsonSerializerSettings.SetSetting();
        return s;
    }
    /// <summary>
    /// 转换为 josn物件
    /// </summary>
    /// <param name="json"></param>
    /// <returns></returns>
    public static JObject Parse(string json)
    {
        //JsonLoadSettings loadSettings = new JsonLoadSettings();

        return JObject.Parse(json);
    }

    /// <summary>
    /// 获取json字符串中某属性的值
    /// </summary>
    /// <param name="json"></param>
    /// <param name="propertyKey">属性KEY</param>
    /// <returns></returns>
    public static object? Parse(string json, string propertyKey)
    {
        //  JsonLoadSettings loadSettings = new JsonLoadSettings();
        return JObject.Parse(json)[propertyKey];
    }

    /// <summary>
    /// 
    /// </summary>
    /// <param name="jobj"></param>
    /// <param name="propertyKey"></param>
    /// <returns></returns>
    public static object? ParseValue(JObject jobj, string propertyKey)
    {
        //  JsonLoadSettings loadSettings = new JsonLoadSettings();
        try
        {
            var o = jobj[propertyKey];
            if (o != null)
            {
                return o;
            }
            return null;
        }
        catch
        {
            return null;

        }
    }

    /// <summary>
    /// 转化为基础类型。bool,数字啥类型？。
    /// </summary>
    /// <param name="json"></param>
    /// <param name="propertyKey"></param>
    /// <returns></returns>
    public static object? ParseValue(string json, string propertyKey)
    {
        try
        {
            var o = JObject.Parse(json)[propertyKey];
            if (o != null)
            {
                return o;
            }
            return null;
        }
        catch
        {
            return null;
        }
    }

    /// <summary>
    /// 转到具体类型
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="jobj"></param>
    /// <param name="propertyKey"></param>
    /// <param name="defaultValue"></param>
    /// <returns></returns>
    public static T? ParseValue<T>(JObject? jobj, string propertyKey, T? defaultValue = default(T))
    {
        try
        {
            if (jobj == null)
            {
                if (defaultValue != null) return defaultValue;
                return default(T);
            }
            //  JsonLoadSettings loadSettings = new JsonLoadSettings();
            var o = jobj[propertyKey];
            if (o != null)
            {
                if (o is JValue jv)
                    return jv.Value<T>();
                else return o.ToObject<T>();
            }
            if (defaultValue != null) return defaultValue;
            return default(T);
        }
        catch
        {
            return default;
        }

    }

    /// <summary>
    /// 转到具体类型
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="json"></param>
    /// <param name="propertyKey"></param>
    /// <param name="defaultValue"></param>
    /// <returns></returns>
    public static T? ParseValue<T>(string? json, string propertyKey, T? defaultValue = default(T))
    {
        try
        {
            if (json.IsNull())
            {
                if (defaultValue != null) return defaultValue;
                return default(T);
            }
            //  JsonLoadSettings loadSettings = new JsonLoadSettings();
            var o = JObject.Parse(json)[propertyKey];
            if (o != null)
            {
                if (o is JValue jv)
                    return jv.Value<T>();
                else return o.ToObject<T>();

            }
            if (defaultValue != null) return defaultValue;
            return default(T);
        }
        catch
        {
            return default;
        }

    }


    /// <summary>
    /// 序列化成文件
    /// </summary>
    /// <param name="value"></param>
    /// <param name="filePath"></param>
    public static void SerializeToFile(object value, string filePath)
    {
        using (System.IO.StreamWriter file = System.IO.File.CreateText(filePath))
        {

            JsonSerializer serializer = JsonSerializer.Create(JsonSerializerSettings);
            serializer.Serialize(file, value);
        }

    }


    /// <summary>
    /// 从文件反序列化。
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <param name="filePath"></param>
    /// <returns></returns>
    public static T? DeserializeFromFile<T>(string filePath)
    {
        using (StreamReader file = File.OpenText(filePath))
        {
            try
            {
                JsonTextReader reader = new JsonTextReader(file);

                Newtonsoft.Json.JsonSerializer serializer = JsonSerializer.Create(JsonSerializerSettings);
                return serializer.Deserialize<T>(reader) ?? default;
            }
            catch
            {

                return default;
            }

        }
    }


    /// <summary>
    /// 从文件反序列化。
    /// </summary>
    /// <param name="type"></param>
    /// <param name="filePath"></param>
    /// <returns></returns>
    public static object? DeserializeFromFile(Type type, string filePath)
    {
        using (StreamReader file = File.OpenText(filePath))
        {
            try
            {

                JsonTextReader reader = new JsonTextReader(file);

                JsonSerializer serializer = JsonSerializer.Create(JsonSerializerSettings);
                return serializer.Deserialize(reader, type) ?? null;
            }
            catch
            {

                return null;
            }

        }
    }

    /// <summary>
    /// 反序列号
    /// </summary>
    /// <param name="value"></param>
    public static T? Deserialize<T>(string? value)
    {
        try
        {
            if (string.IsNullOrWhiteSpace(value)) return default;
            return JsonConvert.DeserializeObject<T>(value, JsonSerializerSettings) ?? default;
        }
        catch (Exception ex)
        {
            Console.WriteLine("JSONDeserializeERR==>:" + typeof(T) + ":==>" + ex.Message);
            throw new Exception("JSONDeserializeERR==>:" + typeof(T) + ":==>" + ex.Message);
            //  throw ex;
        }

    }




    /// <summary>
    /// 
    /// </summary>
    /// <param name="value"></param>
    /// <param name="type"></param>
    /// <returns></returns>
    public static object? Deserialize(string value, Type type)
    {
        try
        {
            if (string.IsNullOrWhiteSpace(value)) return null;
            return JsonConvert.DeserializeObject(value, type, JsonSerializerSettings) ?? null;
        }
        catch
        {
            return null;
        }

    }

}



public class JsonPropertyContractResolver : DefaultContractResolver
{
    IEnumerable<string> lstInclude;
    public JsonPropertyContractResolver(IEnumerable<string> includeProperties)
    {

        lstInclude = includeProperties;
    }

    protected override IList<JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization)
    {

        return base.CreateProperties(type, memberSerialization).ToList().FindAll(p => lstInclude.Contains(p.PropertyName));//需要输出的属性  } }
    }
}



